package cn.ysbd.datafactory.engine;

import cn.ysbd.datafactory.config.JedisPoolFactory;
import cn.ysbd.datafactory.config.RedisKey;
import cn.ysbd.datafactory.engine.entity.LogData;
import cn.ysbd.datafactory.engine.http.URLConnectionHelper;
import cn.ysbd.datafactory.engine.service.LoggerFieldService;
import cn.ysbd.datafactory.utils.RedisLock;
import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import redis.clients.jedis.Jedis;

import java.util.List;

/**
 * @Author: YinHeng
 * @Description: 服务异常日志处理
 * @DateTime: 2022/8/18 10:41
 */
@Component
public class LogDataTask {

    private static final Logger LOGGER = LoggerFactory.getLogger(LogDataTask.class.getName());

    private static final String REQUEST_OK = "success";

    @Autowired
    private LoggerFieldService loggerFieldService;

    @Value("${config.loki.logQL:http://10.52.1.31:3100/loki/api/v1/query_range?query={app=~\"ysbedo-gateway\"}&direction=forward&limit=1000}")
    private String logQL;


    /**
     * loki日志查询,时间跨度不能超过721个小时，最早不能超过
     */
    @Scheduled(cron = "0/10 * * * * *")
    public void lokiQuery() {
        String url = logQL;
        String body = null;


        //获取分布式锁，避免多应用实例重复查询
        RedisLock redisLock = new RedisLock();
        Jedis jedis = null;
        Long time = null;
        try {
            redisLock.lock();
            List<LogData> latestRow = loggerFieldService.list(new QueryWrapper<LogData>()
                    .orderByDesc("ts_ns")
                    .last("limit 1"));

            //获取上次查询的日志的最新一条记录的创建时间，并查询该时间之后增加的日志
            if (latestRow.size() != 0) {
                LogData latestItem = latestRow.get(0);
                time = latestItem.getTsNs();
                time = time + 1;
            } else {
                jedis = JedisPoolFactory.getJedis();
                String timeStr = jedis.get(RedisKey.LOG_DATA_START_TIME);
                jedis.close();
                if (timeStr != null) {
                    time = Long.valueOf(timeStr);
                }
            }
            if (time != null) {
                url += "&start=" + time;
            }

            JSONObject jsonObject = new JSONObject();
            jsonObject.put("lokiRequestUrl", url);
            LOGGER.debug(jsonObject.toString());
            body = URLConnectionHelper.sendRequest(url);
        } catch (Exception e) {
            redisLock.unlock();
            e.printStackTrace();
        } finally {
            redisLock.unlock();
            if (jedis != null) {
                jedis.close();
            }
        }

        if (body == null || "".equals(body)) {
            return;
        }

        //新开一个线程处理数据，避免异常导致定时任务停止
        Thread thread = new Thread(new LogHandler(body, loggerFieldService, time == null));
        thread.start();

    }


}
